package com.yiqixuejava.reconciliation.service.impl;

import com.yiqixuejava.reconciliation.config.RedisUtils;
import com.yiqixuejava.reconciliation.dto.RDetail;
import com.yiqixuejava.reconciliation.entity.SourceEntity;
import com.yiqixuejava.reconciliation.exception.ServiceException;
import com.yiqixuejava.reconciliation.service.ReconService;
import com.yiqixuejava.reconciliation.util.StringUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.sql.*;
import java.util.ArrayList;
import java.util.List;

import static com.yiqixuejava.reconciliation.exception.CoreExceptionEnum.*;

/**
 * 类的描述：mysqlWx获取数据
 *
 * @author: zoux
 * @createDate: 2019/11/15 09:50
 * @version: v1.0
 */
@Slf4j
@Service(value = "MySqlReconWxImpl")
public class MySqlReconWxImpl implements ReconService {

    // 连接数据
    private static Connection conn = null;
    private static Statement stmt = null;
    private static ResultSet bCollect = null;
    // 获取sql语句和调用方
    private static String sourceCode = "";
    // 如果查出时间为空，默认设置时间
    private static final String date = "2019-01-01 00:00:00";

    @Autowired
    private RedisUtils redisUtils;

    /**
     * 对账准备接口，实现方应该准备好对账所需资源
     *
     * @throws ServiceException
     */
    @Override
    public void prepare(SourceEntity sourceEntity) throws ServiceException {
        if (null == sourceEntity) {
            throw new ServiceException(BEAN_NOT_EXIST);
        }
        // 检查所需资源是否准备齐全
        if (StringUtil.stringIsNull(sourceEntity.getSourceCode()) || StringUtil.stringIsNull(sourceEntity.getUri()) || StringUtil.stringIsNull(sourceEntity.getParam1())
                || StringUtil.stringIsNull(sourceEntity.getParam2()) || StringUtil.stringIsNull(sourceEntity.getParam3())) {
            throw new ServiceException(NOT_MYSQL_DATA);
        }

        // 创建jdbc连接数据库需求数据
        try {
            Class.forName(sourceEntity.getParam3());
            conn = DriverManager.getConnection(sourceEntity.getUri(), sourceEntity.getParam1(), sourceEntity.getParam2());
            // 准备sql语句
            stmt = conn.createStatement();
            sourceCode = sourceEntity.getSourceCode();
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

    /**
     * 获取对账数据
     *
     * @return
     */
    @Override
    public List<RDetail> getNextData(int maxSize) throws Exception {

        if (0 == maxSize) {
            throw new ServiceException(MAX_SIZE_NOT);
        }
        // 查询是否有key存入redis，key 是谁在调，value是需要从多少条开始查
        int first = 0;
        if (redisUtils.hasKey(sourceCode)) {
            first = (int) redisUtils.get(sourceCode);
        } else {
            redisUtils.set(sourceCode, first, 0);
        }
        // 获取对应sql，获取数据
        String bCollectSql = "SELECT payment_notice_no,ys_amount,create_time FROM b_collect_wxpay WHERE trade_status = 'SUCCESS' AND create_time BETWEEN '20180825' AND '20180831' LIMIT "
                +first+","+maxSize;
        log.info("MySqlReconWxImpl本次查询起始位置{}，查询条数{}",first,maxSize);
        bCollect = stmt.executeQuery(bCollectSql);
        if (null == bCollect) {
            throw new ServiceException(NOT_RECON_DATA);
        }
        List<RDetail> listAll = convertList(bCollect);

        // 获取完毕将本次查询条数储存
        first += listAll.size();
        redisUtils.set(sourceCode, first);

        return listAll;
    }

    /**
     * 关闭资源接口，如关闭流或者数据库连接
     */
    @Override
    public void destroy() {
        try {
            conn.close();
            stmt.close();
            bCollect.close();
            this.delete();
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    // 把结果集转换成list
    private List convertList(ResultSet rs) throws Exception {

        List list = new ArrayList();
        while (rs.next()) {
            RDetail rDetail = new RDetail();
            rDetail.setOrderNo(rs.getString(1));
            rDetail.setTradeAmount(rs.getString(2));
            if( null == rs.getString(3)){
                rDetail.setTradeDateTime(date);
            } else {
                rDetail.setTradeDateTime(rs.getString(3));
            }
            list.add(rDetail);
        }
        return list;
    }

    //清除redies 缓存
    public void delete(){
        redisUtils.del("MySqlReconImpl");
        redisUtils.del("MySqlReconWxImpl");
        log.info("缓存清理完成");
    }


    }

